/*
 * @(#) SqlBatchUtil.java 2011-4-21
 *
 * Copyright (c) 2010, Strong Technology. All Rights Reserved.
 * Strong Technology. CONFIDENTIAL
 */
package cn.strong.gweva.common.util;

import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import org.springframework.orm.ibatis.SqlMapClientCallback;
import org.springframework.orm.ibatis.support.SqlMapClientDaoSupport;

import com.ibatis.sqlmap.client.SqlMapExecutor;


/**
 *	批量执行SQL
 * 
 * @author lilanfei
 * @version 1.0
 * @since 2011-4-21
 */
public class SqlBatchUtil {
	
	public static final int count = 10000;
	
	/**
	 * INSERT整体提交
	 */
	public static int doInsertBatch(SqlMapClientDaoSupport dao, final String sqlId,
			List<Object> dataList) {
		List<Object> exexuteList = new ArrayList<Object>();
		int insertCount = 0;
		for (int i = 0; i < dataList.size(); i++) {
			exexuteList.add(dataList.get(i));
			
			if ((i != 0 && i % count == 0) || i == dataList.size() - 1) {
				insertCount += SqlBatchUtil.doInsertBatchPartition(dao, sqlId, exexuteList);
				exexuteList = new ArrayList<Object>();
			}
		}
		return insertCount;
	}
	
	/**
	 * INSERT单条提交
	 */
	public static int doInsertBatchPartition(SqlMapClientDaoSupport dao, final String sqlId,
			final List<Object> partitionList) {
		SqlMapClientCallback callback = new SqlMapClientCallback() {
			int result = 0;
			
			public Object doInSqlMapClient(SqlMapExecutor executor) throws SQLException {
				executor.startBatch();
				for (int i = 0; i < partitionList.size(); i++) {
					Object data = partitionList.get(i);
					if (data == null) {
						continue;
					}
					executor.insert(sqlId, data);
					result++;
				}
				executor.executeBatch();
				return new Integer(result);
			}
		};
		
		return ((Integer)dao.getSqlMapClientTemplate().execute(callback)).intValue();
	}
	
	/**
	 * UPDATE整体提交
	 */
	public static int doUpdateBatch(SqlMapClientDaoSupport dao, final String sqlId,
			List<Object> dataList) {
		List<Object> exexuteList = new ArrayList<Object>();
		int updateCount = 0;
		for (int i = 0; i < dataList.size(); i++) {
			exexuteList.add(dataList.get(i));
			
			if ((i != 0 && i % count == 0) || i == dataList.size() - 1) {
				updateCount += SqlBatchUtil.doUpdateBatchPartition(dao, sqlId, exexuteList);
				exexuteList = new ArrayList<Object>();
			}
		}
		return updateCount;
	}
	
	/**
	 * UPDATE单条提交
	 */
	public static int doUpdateBatchPartition(SqlMapClientDaoSupport dao, final String sqlId,
			final List<Object> partitionList) {
		SqlMapClientCallback callback = new SqlMapClientCallback() {
			int result = 0;
			
			public Object doInSqlMapClient(SqlMapExecutor executor) throws SQLException {
				executor.startBatch();
				for (int i = 0; i < partitionList.size(); i++) {
					Object data = partitionList.get(i);
					if (data == null) {
						continue;
					}
					executor.update(sqlId, data);
					result++;
				}
				executor.executeBatch();
				return new Integer(result);
			}
		};
		
		return ((Integer)dao.getSqlMapClientTemplate().execute(callback)).intValue();
	}
	
	/**
	 * DELETE整体提交
	 */
	public static void doDeleteBatch(SqlMapClientDaoSupport dao, final String sqlId,
			List<Object> dataList) {
		List<Object> exexuteList = new ArrayList<Object>();
		for (int i = 0; i < dataList.size(); i++) {
			exexuteList.add(dataList.get(i));
			
			if ((i != 0 && i % count == 0) || i == dataList.size() - 1) {
				SqlBatchUtil.doDeleteBatchPartition(dao, sqlId, exexuteList);
				exexuteList = new ArrayList<Object>();
			}
		}
	}
	
	/**
	 * DELETE单条提交
	 */
	public static void doDeleteBatchPartition(SqlMapClientDaoSupport dao, final String sqlId,
			final List<Object> partitionList) {
		SqlMapClientCallback callback = new SqlMapClientCallback() {
			int result = 0;
			
			public Object doInSqlMapClient(SqlMapExecutor executor) throws SQLException {
				executor.startBatch();
				for (int i = 0; i < partitionList.size(); i++) {
					Object data = partitionList.get(i);
					if (data == null) {
						continue;
					}
					executor.delete(sqlId, data);
					result++;
				}
				executor.executeBatch();
				return new Integer(result);
			}
		};
		
		dao.getSqlMapClientTemplate().execute(callback);
	}
}
